package com.gitee.deament.server.core.cli.db.sortset;

import com.gitee.deament.server.config.SystemConfig;
import com.gitee.deament.server.core.annotation.CliHander;
import com.gitee.deament.server.core.cli.AbstractCli;
import com.gitee.deament.server.core.data.ConnectData;
import com.gitee.deament.server.core.data.ZSortSet;
import com.gitee.deament.server.core.data.ZSortSetMember;
import com.gitee.deament.server.core.data.datatype.Value;
import io.netty.channel.ChannelHandlerContext;
import io.netty.handler.codec.http.websocketx.TextWebSocketFrame;

import java.math.BigDecimal;
import java.util.*;

/**
 * ZADD key score member [[score member] [score member] …]
 * 可用版本： >= 1.2.0
 * 时间复杂度: O(M*log(N))， N 是有序集的基数， M 为成功添加的新成员的数量。
 * 将一个或多个 member 元素及其 score 值加入到有序集 key 当中。
 *
 * 如果某个 member 已经是有序集的成员，那么更新这个 member 的 score 值，并通过重新插入这个 member 元素，来保证该 member 在正确的位置上。
 *
 * score 值可以是整数值或双精度浮点数。
 *
 * 如果 key 不存在，则创建一个空的有序集并执行 ZADD 操作。
 *
 * 当 key 存在但不是有序集类型时，返回一个错误。
 *
 * 对有序集的更多介绍请参见 sorted set 。
 * 返回值
 * 被成功添加的新成员的数量，不包括那些被更新的、已经存在的成员。
 * @author deament
 */
@CliHander(command = "ZADD")
public class ZADDcli extends AbstractCli {
    @Override
    public void executeCli(ChannelHandlerContext channelHandlerContext, String command) {
        List<String> cliValues = getValues(command);
        if (cliValues.size() <4 && cliValues.size()%2!=0) {
            channelHandlerContext.channel().writeAndFlush(new TextWebSocketFrame("ERR wrong number of arguments for 'ZADD' command"));
            return;
        }
        String key = cliValues.get(1);
        int db = ConnectData.SELECT_DB_STORAGE.getUseDB(channelHandlerContext.channel().id().asLongText());
        List<ZSortSetMember > memberList= new ArrayList<>();
        try {
            for (int i = 2; i < cliValues.size(); i = i + 2) {
                BigDecimal score = new BigDecimal(cliValues.get(i));
                String memberName = cliValues.get(i + 1);
                memberList.add(new ZSortSetMember(score, memberName));
            }
        }catch (Exception e){
            channelHandlerContext.channel().writeAndFlush(new TextWebSocketFrame("ERR wrong number of arguments for 'ZADD' command"));
            return;
        }
        try {
            Value<ZSortSet> data = SystemConfig.dbData.getZSortSetData(db, key);
            for (ZSortSetMember member : memberList) {
                SystemConfig.dbData.setZSortSetData(db,key,member);
            }
            channelHandlerContext.channel().writeAndFlush(new TextWebSocketFrame( SystemConfig.dbData.getZSortSetData(db, key).getValue().getData().size()+""));
            return;
        }catch (Exception e){
            channelHandlerContext.channel().writeAndFlush(new TextWebSocketFrame(e.getMessage()));
            return;
        }
    }
}
